package completablefuture;

import lombok.extern.slf4j.Slf4j;
import org.junit.jupiter.api.Test;

import java.util.concurrent.ArrayBlockingQueue;
import java.util.concurrent.CompletableFuture;
import java.util.concurrent.ThreadPoolExecutor;
import java.util.concurrent.TimeUnit;

/**
 * @author ZhuQi
 * @ClassName Demo1
 * @Date 2022/9/5 15:38
 * @Version 1.0
 * @Description 测试CompletableFuture
 */
@Slf4j
public class Demo1 {

    /**
     * 测试内容: 创建  CompletableFuture
     * 测试结果:
     */
    @Test
    public void test() throws Exception {
        ThreadPoolExecutor executor = new ThreadPoolExecutor(4, 4,
                30L, TimeUnit.SECONDS, new ArrayBlockingQueue(10));
        // 不推荐 new 创建 CompletableFuture，这样创建的是不完全的

        // 第一种，无返回值 runAsync
        CompletableFuture<Void> completableFuture1
                = CompletableFuture.runAsync(() -> log.info("---"));
        CompletableFuture<Void> completableFuture2
                = CompletableFuture.runAsync(() -> log.info("---"),executor);

        // 第二种，有返回值的 supplyAsync
        CompletableFuture<String> completableFuture3 =
                CompletableFuture.supplyAsync(() -> "---------");
        CompletableFuture<String> completableFuture4 =
                CompletableFuture.supplyAsync(() -> "---------", executor);


        // 当没有指定线程池，默认使用 ForkJoinPool.commonPool（）做为线程池来执行
        // 如果指定了线程池，使用我们指定的来执行
    }


    /**
     * 测试内容: 执行 runAsync
     * 测试结果: 输出：ForkJoinPool.commonPool-worker-1] INFO completablefuture.Demo1 - ForkJoinPool.commonPool-worker-1
     */
    @Test
    public void test01() throws Exception {
        CompletableFuture<Void> completableFuture = CompletableFuture.runAsync(() -> log.info(Thread.currentThread().getName()));
        completableFuture.get();
    }

    /**
     * 测试内容: 执行 runAsync
     * 测试结果: 输出：[pool-1-thread-1] INFO completablefuture.Demo1 - pool-1-thread-1
     */
    @Test
    public void test02() throws Exception {
        ThreadPoolExecutor executor = new ThreadPoolExecutor(4, 4,
                30L, TimeUnit.SECONDS, new ArrayBlockingQueue(10));
        CompletableFuture<Void> completableFuture = CompletableFuture.runAsync(() -> log.info(Thread.currentThread().getName()), executor);
        completableFuture.get();
        executor.shutdown();
    }

    /**
     * 测试内容: 执行 supplyAsync
     * 测试结果: 有返回值
     */
    @Test
    public void test03() throws Exception {
        CompletableFuture<String> stringCompletableFuture = CompletableFuture.supplyAsync(() -> {
            log.info(Thread.currentThread().getName());
            return "有返回值";
        });
        String s = stringCompletableFuture.get();
        log.info(s);
    }

    /**
     * 测试内容: 执行 supplyAsync
     * 测试结果: 有返回值
     */
    @Test
    public void test04() throws Exception {
        ThreadPoolExecutor executor = new ThreadPoolExecutor(4, 4,
                30L, TimeUnit.SECONDS, new ArrayBlockingQueue(10));
        CompletableFuture<String> stringCompletableFuture = CompletableFuture.supplyAsync(() -> {
            log.info(Thread.currentThread().getName());
            return "有返回值";
        }, executor);
        String s = stringCompletableFuture.get();
        log.info(s);
    }
}
